home *** CD-ROM | disk | FTP | other *** search
- /* cvatt.c
- * attacks, droping things, feeding and other such stuff
- ************************************************************************/
-
- #include <stdio.h>
- #include "cvobj.h"
- #include "cvocab.h"
- #include "cvlocs.h"
- #include "cvmisc.h"
- #include "cvorcs.h"
- #include "cvcode.h"
- #include "random.h"
-
- extern int actspk[]; /* cvocab.c */
- extern char *oword;
- extern void cvsave();
- extern void putcode();
- extern int mutilate();
- extern void newcon();
- extern int drunkbear();
- extern int wakeking();
-
- #define OKAY(msg) {rspeak(msg); return S_okay;}
- #define DEFMSG OKAY(actspk[verb%1000])
- #define BREAKIT {register int i; if (i = mutilate(object)) {\
- newloc = &(cvloc[i]); return S_move;\
- } else return S_okay; }
- #define FILLIT(object,liquid) {(object)->prop = (liquid) - _WATER + 1;}
- #define INTRANS
- #define TRANS 10000 +
-
- static int
- dropit(verb,object) register struct cvobj *object;
- {
- if ((object == ROPE)
- && TOTING(ROPE2)
- && !TOTING(ROPE)) object = ROPE2;
-
- if (TOTING(BOTTLE) && (OBJ(LIQ(BOTTLE))==object)) object = BOTTLE;
-
- if (TOTING(CUP) && (OBJ(LIQ(CUP))==object)) object = CUP;
-
- if (!TOTING(object)) DEFMSG;
-
- if ((object == WALLET) && (HERE(VEND)) && (VEND->prop == 0))
- { if (object->prop == 4)
- { pspeak(object,4);
- rspeak(54);
- } else {
- object->prop++;
- VEND->prop = 1;
- move(BOTTLE,loc);
- pspeak(BOTTLE,BOTTLE->prop);
- return S_okay;
- }
- } else if (object == RUG)
- { register int k;
- k = RUG->prop;
- RUG->prop = 0;
- if (k) {
- if ((loc - cvloc) > 30)
- { if (drownch()) {
- return S_move;
- } else {
- rspeak(54);
- }
- } else {
- destry(RUG);
- pspeak(RUG,2);
- return S_okay;
- }
- } else {
- rspeak(54);
- }
- } else if (object == BOAT)
- { object->prop -= 2;
- if (loc->flags & DROWN)
- { rspeak(120);
- oldlc2 = loc;
- die();
- return S_move;
- }
- rspeak(54);
- } else if ((object == SEARS)
- && (((loc - cvloc) == SEARS->iloc)
- || ((loc - cvloc) == 78) ) )
- { object->prop = 1;
- move2(SEARS,&(cvloc[78 + (SEARS->iloc) - (loc - cvloc)]));
- pspeak(object,1);
- } else if (object == FOOD && HERE(DRAGON)) {
- rspeak(166); /* tell him the dragon doesn't eat that */
- } else {
- rspeak(54); /* okay */
- }
-
- move(object,loc);
- if (HERE(ORCS) && ORCS->prop)
- { if (((object == CUP) || (object == BOTTLE))
- && (LIQ(object) == _COLA))
- { didorc();
- return S_okay;
- }
- pspeak(ORCS,2); /* the orcs don't like that */
- }
-
- if ((object == CHEST) && (SKELTN->prop == 1))
- { SKELTN->prop = 2;
- rspeak(97); /* skeleton crumples */
- }
-
- return S_okay;
- }
-
- int
- cvatt(verb,obj,object) register int verb,obj;
- register struct cvobj *object;
- { register int k;
-
- switch ((!!obj*10000) + verb) {
-
- case TRANS DROP:
- return dropit(verb,object);
-
- case TRANS THROW:
- /* throw is like pour for liquids. For axe, something might get killed.
- Otherwise, it is the same as "drop".
- The axe is the only way to deal with some things, and is special for
- the bugbear (as is the keg, food, keys.)
- Sand is special for the Balrog.
- Spice is special for the dragon.
- */
- if ((object == WATER) || (object == WINE) ||(object == COLA))
- { goto L9130;
- }
-
- if ((object == ROPE) && TOTING(ROPE2) && !TOTING(object)) {
- object = ROPE2;
- }
-
- if (!TOTING(object)) DEFMSG;
-
- if (BEAR->prop && HERE(BEAR)) {
- if ((object == KEY) && (CHAIN->prop == 2)) {
- move(KEY,loc);
- CHAIN->prop = 0;
- destr2(CHAIN);
- rspeak(151); /* the bugbear is no slouch */
- BEAR->prop -= 2;
- YOGI->dseen = TRUE;
- YOGI->dloc = loc;
- return S_show;
- }
- if ((object == KEG)
- || (((object == CUP) || (object == BOTTLE))
- && (LIQ(object) == _WINE))) {
- return drunkbear(object);
- }
- }
-
- if ((object == HAMMER) && HERE(SKELTN) && (SKELTN->prop == 1)) {
- HAMMER->prop = SKELTN->prop = 0;
- pspeak(HAMMER,2);
- move(HAMMER,loc);
- /* let's not be annoyed with curses or odd things about
- "take" when pirate is really inactive */
- PIRATE->dloc = PIRATE->oloc = DEAD;
- PIRATE->dseen = FALSE;
- newloc = loc;
- return S_move;
- }
-
- if ((object == SPICE) && HERE(DRAGON)) {
- destry(SPICE);
- destry(DRAGON);
- DRAGON->prop = 0;
-
- PUFF->dseen = TRUE; /* now for the really annoying dragon */
- PUFF->dloc = loc;
- OKAY(148); /* the bad news */
- }
-
- if ((object == SAND) && (BALLY->dloc = loc)) {
- pspeak(SAND,1);
- destry(SAND);
- pspeak(BALROG,1);
- BALROG->prop = 0;
- move(BALROG,&(cvloc[62]));
- BALLY->dseen = FALSE;
- BALLY->dloc = DEAD;
- return S_okay;
- }
-
- if (object == FOOD) {
- goto L8210; /* treat as FEED */
- }
-
- /* non-weapons just get dropped here and that's it */
- if ((object != AXE) /* note: AXE is not among weapons */
- && ((object <= MINWPN) || (object >= MAXWPN))) {
- return dropit(verb,object);
- }
-
- move(object,loc); /* weapons also end up here */
- /* he may kill any dwarf, the kobold, or sometimes even the giant */
- /* but with multiple targets, we hit the easy ones first */
- if (SLASHER->dloc == loc) {
- KOBOLD->prop = 3;
- move(KOBOLD,loc);
- KOBOLD->conn2.where = FIXED;
- SLASHER->dseen = FALSE;
- SLASHER->dloc = DEAD;
- rspeak(150);
- newloc = loc;
- return S_move;
- }
-
- { register struct monster *cre;
- for (cre = MINDWR; cre <= MAXDWR; cre++) {
- if (cre->dloc == loc) {
- if (PCT(67) && (saved == -1)) {
- cre->dseen = FALSE;
- cre->dloc = DEAD;
- dflag++; /* annoy them some more */
- rspeak(++dkill == 1 ? 149 : 47);
- } else {
- rspeak(48);
- }
- newloc = loc;
- return S_move;
- }
- }
- }
-
- if (HERE(GIANT) && GIANT->prop) {
- pspeak(GIANT,3);
- oldlc2 = loc;
- die();
- return S_show;
- }
-
- if (HERE(BEAR) && BEAR->prop) {
- move2(AXE,FIXED);
- AXE->prop = 1;
- if (HERE(CHAIN) && !TOTING(CHAIN)) juggle(CHAIN);
- juggle(BEAR);
- OKAY(164);
- }
-
- if (SKELTN->prop == 1) {
- rspeak(141);
- newloc = loc;
- return S_show;
- }
-
- if (ME->dloc == loc) return suicide();
-
- { register struct monster *cre;
- for (cre = orcs; cre->iloc >= 0; ++cre) {
- if (cre->dloc == loc) {
- rspeak(141);
- newloc = loc;
- return S_show;
- }
- }
- }
-
- carry(object); /* well, pick it up again */
- return dropit(verb,object); /* and just drop the damned thing */
-
- case INTRANS FEED:
- L8210: obj = 0;
- if (HERE(BEAR)
- && (BEAR->prop == 2 || BEAR->prop == 4)) obj = _BEAR;
- if (dflag >= 2) {
- register struct monster *cre;
- if (HERE(UNICRN)
- && (UNICRN->prop)
- && (!obj || PCT(75))) obj = _UNICRN;
- for (cre = MINDWR; cre <= MAXDWR; ++cre) {
- if ((cre->dloc == loc) && ( !obj || PCT(50))) obj = _DWARF;
- }
- }
- if (!obj) { /* nobody here to feed */
- if (verb != THROW) return S_what; /* normally, just complain */
- obj = _FOOD; /* but if he said "throw food" */
- object = OBJ(obj); /* we instead . . . */
- return dropit(verb,object); /* just drop it */
- }
- object = OBJ(obj);
- case TRANS FEED:
- if (!HERE(FOOD)) DEFMSG;
- if (object == DWARF) {
- dflag += 8; /* get them mad */
- OKAY(103);
- }
- if (object == UNICRN && UNICRN->prop) return unicorn();
- if (object == BEAR
- && (BEAR->prop == 2 || BEAR->prop == 4)) {
- pspeak(BEAR, --(BEAR->prop));
- destry(FOOD);
- return S_okay;
- }
- OKAY(14);
-
- case INTRANS POUR:
- obj = 0;
- if (TOTING(BOTTLE) && LIQ(BOTTLE)) obj = LIQ(BOTTLE);
- if (TOTING(CUP) && LIQ(CUP)) obj = (obj << 10) + LIQ(CUP);
- if (!obj || (obj > 2000)) return S_what;
- object = OBJ(obj);
- case TRANS POUR:
- L9130: k = 0; /* from THROW (indirectly from FEED, too) */
- if (TOTING(BOTTLE) && LIQ(BOTTLE) == obj) k = _BOTTLE;
- if (TOTING(CUP) && LIQ(CUP) == obj) k = (k << 10) + _CUP;
- if (k > 2000) OKAY(143); /* from what? */
- if (k) object = OBJ(obj=k);
- if (!TOTING(object)) DEFMSG;
- if (object != CUP && object != BOTTLE) OKAY(78); /* cannot */
- k = LIQ(object);
- if (!k) {
- pspeak(object,11); /* but it's empty */
- return S_okay;
- }
- if (verb == THROW) {
- if (k == _WINE && HERE(BEAR) && BEAR->prop) {
- return drunkbear(object);
- } else {
- rspeak(k == _WATER ? 77 : 79);
- }
- } else {
- obj = object - cvobj;
- obj = _CUP + _BOTTLE - obj;
- if (OBJ(obj)->prop == 0 && HERE(OBJ(obj))) {
- OBJ(obj)->prop = object->prop;
- pspeak(OBJ(obj),object->prop + 7);
- } else {
- rspeak(k == _WATER ? 77 : 79);
- }
- }
- object->prop = 0;
- newcon(object,7,k);
- return S_show;
-
- case INTRANS FILL:
- obj = 0;
- if (TOTING(CUP)) {
- if (TOTING(BOTTLE)) {
- if (!(BOTTLE->prop) && !(CUP->prop)) {
- return S_what; /* can't tell which one */
- } else {
- obj = CUP->prop ? _BOTTLE : _CUP;
- }
- } else obj = _CUP;
- } else if (TOTING(BOTTLE)) obj = _BOTTLE;
- if (!obj) return S_what;
- object = OBJ(obj);
- case TRANS FILL:
- if (object != BOTTLE && object != CUP) DEFMSG;
- if (!TOTING(object)) OKAY(29);
- if (object->prop) {pspeak(object,12); return S_show; }
- if (!(k = LIQLOC(loc))) {
- obj = _CUP + _BOTTLE - obj;
- if (HERE(OBJ(obj))) k = LIQ(OBJ(obj));
- if (!k) OKAY(106);
- pspeak(OBJ(obj),7); /* announce source is now empty */
- OBJ(obj)->prop = 0;
- }
- newcon(object,(object->prop=k-_WATER+1)+7, k); /* announce result */
- return S_show;
-
- default:
- fputs("Unknown verb in cvatt.\n",stdout);
- return S_okay;
- }
- }
-
-